package com.seele.tigerwallet.ui.activtiy;

import android.app.Activity;
import android.content.Intent;
import android.content.res.AssetFileDescriptor;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.RectF;
import android.graphics.SurfaceTexture;
import android.media.AudioManager;
import android.media.MediaPlayer;
import android.media.SoundPool;
import android.net.Uri;
import android.os.Build;
import android.os.Vibrator;
import android.provider.MediaStore;
import android.support.annotation.Nullable;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.support.v7.widget.Toolbar;
import android.text.TextUtils;
import android.view.TextureView;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import android.view.WindowManager;
import android.widget.TextView;
import android.widget.Toast;

import com.google.zxing.Constant;
import com.google.zxing.activity.CaptureActivity;
import com.seele.tigerwallet.R;
import com.seele.tigerwallet.ui.base.BaseActivity;
import com.seele.tigerwallet.ui.base.TitleBaseActivity;
import com.seele.tigerwallet.ui.utils.StatusBarUtil;
import com.seele.tigerwallet.ui.utils.StatusBarUtils;

import org.json.JSONObject;

import java.io.IOException;

import cn.simonlee.xcodescanner.core.CameraScanner;
import cn.simonlee.xcodescanner.core.GraphicDecoder;
import cn.simonlee.xcodescanner.core.NewCameraScanner;
import cn.simonlee.xcodescanner.core.OldCameraScanner;
import cn.simonlee.xcodescanner.core.ZBarDecoder;
import cn.simonlee.xcodescanner.view.AdjustTextureView;
import cn.simonlee.xcodescanner.view.ScannerFrameView;

/**
 * @author YangJ 二维码扫描界面
 */
public class ScanActivity extends BaseActivity implements CameraScanner.CameraListener,
        TextureView.SurfaceTextureListener {

    private static final float BEEP_VOLUME = 0.10f;
    private static final long VIBRATE_DURATION = 200L;
    // 点击相册按钮跳转至系统相册界面请求码
    private static final int REQUEST_CODE_PHOTO = 1;
    private static final int PICK_LOCAL_PHOTO_SUCCESS = 100;

    private int key;
    // 二维码解析次数，连续4次解析结果相同则认为解析成功
    private int mCount;
    // 二维码解析结果
    private String mResult;
    private CameraScanner mCameraScanner;
    private GraphicDecoder mGraphicDecoder;
    private int mSoundId;
    private SoundPool mSoundPool;
    // View
    private AdjustTextureView mTextureView;
    private ScannerFrameView mScannerFrameView;

    @Override
    protected int getLayoutId() {
        return R.layout.activity_scan;
    }

    @Override
    protected void init() {
        initWidow();
        initData();
        initView();
        initSound();
    }

    @Override
    protected void onRestart() {
        if (mTextureView.isAvailable()) {
            // 部分机型转到后台不会走onSurfaceTextureDestroyed()，因此isAvailable()一直为true，转到前台后不会再调用onSurfaceTextureAvailable()
            // 因此需要手动开启相机
            mCameraScanner.setSurfaceTexture(mTextureView.getSurfaceTexture());
            mCameraScanner.setPreviewSize(mTextureView.getWidth(), mTextureView.getHeight());
            mCameraScanner.openCamera(this.getApplicationContext());
        }
        super.onRestart();
    }

    @Override
    protected void onPause() {
        mCameraScanner.closeCamera();
        super.onPause();
    }

    @Override
    protected void onDestroy() {
        mCameraScanner.setGraphicDecoder(null);
        if (mGraphicDecoder != null) {
            mGraphicDecoder.setDecodeListener(null);
            mGraphicDecoder.detach();
        }
        mCameraScanner.detach();
        super.onDestroy();
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        if (REQUEST_CODE_PHOTO == requestCode && Activity.RESULT_OK == resultCode && data != null) {
            mCount = PICK_LOCAL_PHOTO_SUCCESS;
            // 获取从相册选择的图片路径，并解析该图片
            onDecodeForResult(data.getData(), requestCode);
        }
    }

    /**
     * 初始化基础数据
     */
    private void initData() {
        Bundle bundle = getIntent().getExtras();
        if (null != bundle) {
            key = bundle.getInt(CaptureActivity.class.getSimpleName());
        }
        /**
         * 注意，SDK21的设备是可以使用NewCameraScanner的，但是可能存在对新API支持不够的情况，比如红米Note3（双网通Android5.0.2）
         * 开发者可自行配置使用规则，比如针对某设备型号过滤，或者针对某SDK版本过滤。此处针对华为系列手机过滤
         **/
        if (isHuawei() || Build.VERSION.SDK_INT <= Build.VERSION_CODES.LOLLIPOP) {
            mCameraScanner = OldCameraScanner.getInstance();
        } else {
            mCameraScanner = NewCameraScanner.getInstance();
        }
        mCameraScanner.setCameraListener(this);
    }

    /**
     * 初始化界面视图
     */
    private void initView() {
        findViewById(R.id.title_back_ll).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                finish();
            }
        });
        TextView tvTitle = findViewById(R.id.title_tv);
        tvTitle.setText(R.string.qrcode_scan);
        TextView tvRight = findViewById(R.id.right_tv);
        tvRight.setText(R.string.photo);
        tvRight.setVisibility(View.VISIBLE);
        tvRight.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Intent intent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
                startActivityForResult(intent, REQUEST_CODE_PHOTO);
            }
        });
        mTextureView = findViewById(R.id.textureView);
        mTextureView.setSurfaceTextureListener(this);
        mScannerFrameView = findViewById(R.id.scannerFrameView);
    }

    /**
     * 初始化音效
     */
    private void initSound() {
        mSoundPool = new SoundPool(1, AudioManager.STREAM_MUSIC, 0);
        AssetFileDescriptor descriptor = null;
        try {
            descriptor = getResources().openRawResourceFd(R.raw.beep);
            mSoundId = mSoundPool.load(descriptor, 1);
        } finally {
            if (descriptor != null) {
                try {
                    descriptor.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    /**
     * 获取从相册选择的图片路径，并解析该图片
     *
     * @param uri         参数为从相册返回的图片uri
     * @param requestCode 参数为请求跳转系统相册的请求码
     */
    private void onDecodeForResult(Uri uri, int requestCode) {
        String[] columns = {MediaStore.Images.Media.DATA};
        Cursor cursor = null;
        try {
            cursor = getContentResolver().query(uri, columns, null,
                    null, null);
            if (cursor.moveToFirst()) {
                int columnIndex = cursor.getColumnIndex(columns[0]);
                String path = cursor.getString(columnIndex);
                // 针对该二维码扫描框架进行优化，需要对图片进行压缩处理，不然会解析失败
                BitmapFactory.Options options = new BitmapFactory.Options();
                options.inJustDecodeBounds = true;
                BitmapFactory.decodeFile(path, options);
                options.inJustDecodeBounds = false;
                int sampleSize = (int) (options.outHeight / (float) 700);
                if (sampleSize <= 0) {
                    sampleSize = 1;
                }
                options.inSampleSize = sampleSize;
                Bitmap bitmap = BitmapFactory.decodeFile(path, options);
                RectF rectF = new RectF(0, 0, bitmap.getWidth(), bitmap.getHeight());
                mGraphicDecoder.decodeForResult(bitmap, rectF, requestCode);
            }
        } finally {
            if (cursor != null) {
                cursor.close();
            }
        }
    }

    /**
     * 获取二维码解析的结果
     *
     * @param result 参数为二维码解析的结果
     */
    private void onDecodeComplete(String result) {
        if (result.equals(mResult)) {
            // 连续四次相同则显示结果（主要过滤脏数据，也可以根据条码类型自定义规则）
            if (mCount <= PICK_LOCAL_PHOTO_SUCCESS && ++mCount > 3) {
                mCount += PICK_LOCAL_PHOTO_SUCCESS;
                onPlaySound();
                try {
                    JSONObject obj = new JSONObject(result);
                    String address = (String) obj.get("WalletAddress");
                    if (TextUtils.isEmpty(address)) {
                        throw new Exception("WalletAddress");
                    }
                    String coinName = (String) obj.get("CoinName");
                    if (TextUtils.isEmpty(coinName)) {
                        throw new Exception("CoinName");
                    }
                    String symbolId = (String) obj.get("CoinSymbolID");
                    if (TextUtils.isEmpty("CoinSymbolID")) {
                        throw new Exception("CoinName");
                    }

                } catch (Exception e) {
                    e.printStackTrace();
                    Toast.makeText(this, getString(R.string.qrcode_error), Toast.LENGTH_SHORT).show();
                    this.finish();
                    return;
                }
                if (key == CaptureActivity.ASSETSF) {
                    Intent resultIntent = new Intent(this, TransferTokenActivity.class);
                    Bundle bundle = new Bundle();
                    bundle.putString(Constant.INTENT_EXTRA_KEY_QR_SCAN, result);
                    resultIntent.putExtras(bundle);
                    startActivity(resultIntent);
                } else {
                    Intent resultIntent = new Intent();
                    Bundle bundle = new Bundle();
                    bundle.putString(Constant.INTENT_EXTRA_KEY_QR_SCAN, result);
                    // 不能使用Intent传递大于40kb的bitmap，可以使用一个单例对象存储这个bitmap
                    //bundle.putParcelable("bitmap", barcode);
                    //Logger.d("saomiao",resultString);
                    resultIntent.putExtras(bundle);
                    this.setResult(RESULT_OK, resultIntent);
                }
                finish();
            }
        } else {
            mCount = 1;
            mResult = result;
        }
    }

    /**
     * 判断用户是否执行从系统相册选择图片进行二维码解析
     *
     * @return true表示用户从系统相册选择图片
     */
    private boolean isPickLocalPhoto() {
        if (PICK_LOCAL_PHOTO_SUCCESS == mCount) {
            return true;
        }
        return false;
    }

    /**
     * 判断是否为华为手机，如果是华为荣耀系列手机，需要使用旧版本api
     *
     * @return
     */
    private boolean isHuawei() {
        if (Build.BRAND.equals("HUAWEI") || Build.BRAND.equals("HONOR")) {
            return true;
        }
        return false;
    }

    /**
     * 发出声音并震动
     */
    private void onPlaySound() {
        AudioManager audioService = (AudioManager) getSystemService(AUDIO_SERVICE);
        if (audioService.getRingerMode() != AudioManager.RINGER_MODE_NORMAL) {
            return;
        }
        // 声音
        mSoundPool.play(mSoundId, 0.5f, 0.5f, 1, 0, 1);
        // 震动
        Vibrator vibrator = (Vibrator) getSystemService(VIBRATOR_SERVICE);
        vibrator.vibrate(VIBRATE_DURATION);
    }

    @Override
    public void openCameraSuccess(int surfaceWidth, int surfaceHeight, int surfaceDegree) {
        mTextureView.setImageFrameMatrix(surfaceWidth, surfaceHeight, surfaceDegree);
        if (mGraphicDecoder == null) {
            // 使用带参构造方法可指定条码识别的格式，根据项目需求仅识别二维码
            mGraphicDecoder = new ZBarDecoder(new int[]{ZBarDecoder.QRCODE});
            mGraphicDecoder.setDecodeListener(new GraphicDecoder.DecodeListener() {
                @Override
                public void decodeComplete(String result, int type, int quality, int requestCode) {
                    if (TextUtils.isEmpty(result)) {
                        // 判断用户是否从系统相册选择图片，如果是，则弹出toast提示二维码无法识别
                        if (isPickLocalPhoto()) {
                            Toast.makeText(ScanActivity.this, R.string.qrcode_error,
                                    Toast.LENGTH_SHORT).show();
                            finish();
                        }
                        return;
                    }
                    if (isPickLocalPhoto()) {
                        mResult = result;
                    }
                    onDecodeComplete(result);
                }
            });
        }
        // 该区域坐标为相对于父容器的左上角顶点。
        // TODO 应考虑TextureView与ScannerFrameView的Margin与padding的情况
        mCameraScanner.setFrameRect(mScannerFrameView.getLeft(), mScannerFrameView.getTop(),
                mScannerFrameView.getRight(), mScannerFrameView.getBottom());
        mCameraScanner.setGraphicDecoder(mGraphicDecoder);
    }

    @Override
    public void openCameraError() {
        // error
        finish();
    }

    @Override
    public void noCameraPermission() {
        // no permission
        finish();
    }

    @Override
    public void cameraDisconnected() {
        // disconnect
        finish();
    }

    @Override
    public void onSurfaceTextureAvailable(SurfaceTexture surfaceTexture, int width, int height) {
        mCameraScanner.setSurfaceTexture(surfaceTexture);
        mCameraScanner.setPreviewSize(width, height);
        mCameraScanner.openCamera(getApplicationContext());
    }

    @Override
    public void onSurfaceTextureSizeChanged(SurfaceTexture surfaceTexture, int width, int height) {

    }

    @Override
    public boolean onSurfaceTextureDestroyed(SurfaceTexture surfaceTexture) {
        // return false;
        return true;
    }

    @Override
    public void onSurfaceTextureUpdated(SurfaceTexture surfaceTexture) {

    }

    /**
     * When the beep has finished playing, rewind to queue up another one.
     */
    private final MediaPlayer.OnCompletionListener beepListener = new MediaPlayer.OnCompletionListener() {
        public void onCompletion(MediaPlayer mediaPlayer) {
            mediaPlayer.seekTo(0);
        }
    };
}